package com.example.chainsave.upload.controller;

import com.example.chainsave.common.annotation.LoginRequired;
import com.example.chainsave.common.model.Result;
import com.example.chainsave.common.util.ChainSaveConstant;
import com.example.chainsave.common.util.HostHolder;
import com.example.chainsave.upload.dto.PasswordDTO;
import com.example.chainsave.upload.entity.User;
import com.example.chainsave.upload.service.UserService;
import com.google.code.kaptcha.Producer;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.*;

import javax.imageio.ImageIO;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.io.OutputStream;
import java.util.List;
import java.util.Map;

@Controller
public class UserController implements ChainSaveConstant {
    private static final Logger logger = LoggerFactory.getLogger(UserController.class);
    @Autowired
    private UserService userService;
    @Autowired
    private Producer kaptchaProducer;
    @Value("${server.servlet.context-path}")
    private String contextPath;
    @Autowired
    private HostHolder hostHolder;

    @RequestMapping(path = "/register", method = RequestMethod.POST)
    @ResponseBody
    public Result<String> register(User user) {
        Map<String, Object> map = userService.register(user);
        if (map == null || map.isEmpty()) {
            return new Result<String>().setMessage("添加用户成功");
        } else {
            return new Result<String>().setParameterErrorMsgInfo(map.get("errorMsg").toString());
        }
    }

    @RequestMapping(path = "/kaptcha", method = RequestMethod.GET)
    public void getKaptcha(HttpServletResponse response, HttpSession session) {
        //生成验证码
        String text = kaptchaProducer.createText();
        BufferedImage image = kaptchaProducer.createImage(text);
        //将验证码存入session
        session.setAttribute("kaptcha", text);
        //将图片输出给浏览器
        response.setContentType("image/png");
        try {
            OutputStream os = response.getOutputStream();
            ImageIO.write(image, "png", os);
        } catch (IOException e) {
            logger.error("响应验证码失败：" + e.getMessage());
        }
    }

    @RequestMapping(path = "/login", method = RequestMethod.POST)
    @ResponseBody
    public Result<User> login(User user, HttpServletResponse response) {
        //检查验证码
//        String kaptcha= (String) session.getAttribute("kaptcha");
//        if(StringUtils.isBlank(code)||StringUtils.isBlank(kaptcha)||!kaptcha.equalsIgnoreCase(code)){
//            return new Result<String>().setParameterErrorMsgInfo("验证码不正确");
//        }
        //检查账号,密码
        int expiredSeconds = user.isRememberMe() ? REMEMBER_EXPIRED_SECONDS : DEFAULT_EXPIRED_SECONDS;
        Map<String, Object> map = userService.login(user.getUsername(), user.getPassword(), expiredSeconds);
        if (map.containsKey("ticket")) {
            Cookie cookie = new Cookie("ticket", map.get("ticket").toString());
            cookie.setPath(contextPath);
            cookie.setMaxAge(expiredSeconds);
            response.addCookie(cookie);
            user = (User) map.get("user");
            user.setPassword(null);
            user.setSalt(null);
            return new Result<User>().setMessage("登陆成功").setData(user);
        } else {
            return new Result<User>().setParameterErrorMsgInfo(map.get("errorMsg").toString());
        }
    }

    @RequestMapping(path = "/logout", method = RequestMethod.GET)
    @ResponseBody
    public Result<String> logout(@CookieValue("ticket") String ticket) {
        userService.logout(ticket);
        return new Result<String>().setMessage("登出成功");
    }

    @RequestMapping(path = "/forget/code", method = RequestMethod.GET)
    @ResponseBody
    public Result<String> sendVerifyCode(PasswordDTO passwordDTO, HttpSession session) {
        Map<String, Object> map = userService.sendVerifyCode(passwordDTO.getEmail());
        if (map.containsKey("verifyCode")) {
            session.setAttribute("verifyCode", map.get("verifyCode"));
            return new Result<String>().setMessage("验证码发送成功");
        } else {
            return new Result<String>().setParameterErrorMsgInfo(map.get("errorMsg").toString());
        }
    }

    @RequestMapping(path = "/forget", method = RequestMethod.POST)
    @ResponseBody
    public Result<String> forgetPassword(PasswordDTO passwordDTO, HttpSession session) {
        //检查验证码
        String code = (String) session.getAttribute("verifyCode");
        if (StringUtils.isBlank(passwordDTO.getVerifyCode()) || StringUtils.isBlank(code) ||
                !code.equals(passwordDTO.getVerifyCode())) {
            return new Result<String>().setParameterErrorMsgInfo("验证码不正确");
        }
        Map<String, Object> map = userService.resetPassword(passwordDTO.getEmail(), passwordDTO.getNewPassword());
        if (map == null || map.isEmpty()) {
            return new Result<String>().setMessage("密码重置成功");
        } else {
            return new Result<String>().setParameterErrorMsgInfo(map.get("errorMsg").toString());
        }
    }

    // 修改密码
    @LoginRequired
    @RequestMapping(path = "/updatePassword", method = RequestMethod.POST)
    @ResponseBody
    public Result<String> updatePassword(PasswordDTO passwordDTO) {
        User user = hostHolder.getUser();
        Map<String, Object> map = userService.updatePassword(user.getId(), passwordDTO.getOldPassword(),
                passwordDTO.getNewPassword());
        if (map == null || map.isEmpty()) {
            return new Result<String>().setMessage("密码更新成功");
        } else {
            return new Result<String>().setParameterErrorMsgInfo(map.get("errorMsg").toString());
        }
    }

    //列出所有用户
    @LoginRequired
    @RequestMapping(path = "/selectAll", method = RequestMethod.GET)
    @ResponseBody
    public Result<List<User>> selectAll() {
        return new Result<List<User>>().setMessage("用户列表获取成功").setData(userService.selectAll());
    }

    //删除用户
    @LoginRequired
    @GetMapping(path = "/deleteUserById/{id}")
    @ResponseBody
    public Result<String> deleteUserById(@PathVariable Integer id) {
        Map<String, Object> map = userService.deleteUserById(id);
        if (map == null || map.isEmpty()) {
            return new Result<String>().setMessage("删除用户成功");
        } else {
            return new Result<String>().setParameterErrorMsgInfo(map.get("errorMsg").toString());
        }
    }

    //更改用户权限
    @LoginRequired
    @RequestMapping(path = "/updateType", method = RequestMethod.POST)
    @ResponseBody
    public Result<String> updateStatus(User user) {
        Map<String, Object> map = userService.updateType(user.getId(), user.getType());
        if (map == null || map.isEmpty()) {
            return new Result<String>().setMessage("更改用户权限成功");
        } else {
            return new Result<String>().setParameterErrorMsgInfo(map.get("errorMsg").toString());
        }
    }

    //用户更改自己的邮箱
    @LoginRequired
    @RequestMapping(path = "/updateEmail", method = RequestMethod.POST)
    @ResponseBody
    public Result<String> updateEmail(User user) {
        Map<String, Object> map = userService.updateEmail(user.getId(), user.getEmail());
        if (map == null || map.isEmpty()) {
            return new Result<String>().setMessage("更改用户邮箱成功");
        } else {
            return new Result<String>().setParameterErrorMsgInfo(map.get("errorMsg").toString());
        }
    }
}
